package self.crypt.web;

import java.io.IOException;
import java.util.List;
import java.util.logging.Level;
import java.util.logging.Logger;

import javax.jdo.PersistenceManager;
import javax.jdo.PersistenceManagerFactory;
import javax.jdo.Query;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.bouncycastle.crypto.CryptoException;

import self.crypt.db.SaveEncryptedData;
import self.crypt.factory.PMF;
import self.crypt.logic.EncryptAndDecrypt;

public class DecryptorServlet  extends HttpServlet {
	private static final long serialVersionUID = -9034435885543980291L;
	private static final Logger log = Logger.getLogger(DecryptorServlet.class.getName());
	public void doGet(HttpServletRequest request, HttpServletResponse response)
	throws IOException {
		PersistenceManager pmf = null;
		String operationName=request.getParameter("operationName");
		if(operationName == null){
			log.info("Operation name is null so let me fetch the crytp datas of the user");
			String emailAddressParam = request.getUserPrincipal().getName();
			pmf = PMF.get().getPersistenceManager();
			Query query = pmf.newQuery(SaveEncryptedData.class);
			query.setFilter("emailAddress==emailAddressParam");
			query.declareParameters("String emailAddressParam");
			try{
				List<SaveEncryptedData> encryptedDataList=(List<SaveEncryptedData>)query.execute(emailAddressParam);
				for(SaveEncryptedData sed:encryptedDataList){
					log.info("Data received is ::"+sed.toString());
				}
				request.setAttribute("dataToDisplay", encryptedDataList);
			}catch(Exception e){
				log.log(Level.SEVERE, "Some exception", e);
				response.sendError(response.SC_INTERNAL_SERVER_ERROR,e.getMessage());
			}
			finally{
				query.closeAll();
			}
			try {
				getServletConfig().getServletContext().getRequestDispatcher("/util/decrypt.jsp").forward(request, response);
			} catch (ServletException e) {
				response.sendError(response.SC_INTERNAL_SERVER_ERROR,e.getMessage());
			}
		}
		else if(operationName.equals("decryptData")){
			log.info("Operation name is decryptData so let me decrypt");
			String passPhrase=request.getParameter("passPhrase");
			String id=request.getParameter("idToDecrypt");
			pmf = PMF.get().getPersistenceManager();
			SaveEncryptedData sed=pmf.getObjectById(SaveEncryptedData.class, new Long(id));
			try {
				String decryptedData=decryptData(passPhrase, sed.getEncryptedData());
				request.setAttribute("decryptedData", decryptedData);
			} catch (CryptoException e) {
				response.sendError(response.SC_INTERNAL_SERVER_ERROR,e.getMessage());
			}
			finally{
				if(pmf!=null){
				pmf.close();
				}
			}
			try {
				System.out.println(getServletConfig());
				System.out.println(getServletConfig().getServletContext());
				System.out.println(getServletConfig().getServletContext().getRequestDispatcher("/util/decrypt.jsp"));
			    getServletConfig().getServletContext().getRequestDispatcher("/util/decrypt.jsp").forward(request, response);
			} catch (ServletException e) {
			    	e.printStackTrace();
				response.sendError(response.SC_INTERNAL_SERVER_ERROR,e.getMessage());
			}
		}
	}
	
	private String decryptData(String key, byte[] data) throws CryptoException {
		EncryptAndDecrypt encAndDec = new EncryptAndDecrypt(key);
		String returnString = encAndDec.decryptString(data);
		return returnString;
	}
	
	public void doPost(HttpServletRequest request, HttpServletResponse response) throws IOException{
		doGet(request,response);
	}
}
